package com.ruoyi.web.controller.data;

import com.ruoyi.base.domain.BaseLimit;
import com.ruoyi.base.service.IBaseLimitService;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.enums.SystemType;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.data.domain.*;
import com.ruoyi.data.service.IDataGoldService;
import com.ruoyi.data.service.IDataInventoryRecordService;
import com.ruoyi.data.service.IDataInventoryService;
import com.ruoyi.data.service.IDataSaleService;
import com.ruoyi.system.service.ISysUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletResponse;
import java.util.List;

/**
 * 订单信息Controller
 *
 * @author zzp
 * @date 2022-10-03
 */
@RestController
@RequestMapping("/data/sale")
public class DataSaleController extends BaseController {
    @Autowired
    private IDataSaleService dataSaleService;

    @Autowired
    private IDataGoldService goldService;

    @Autowired
    private IDataInventoryService inventoryService;

    @Autowired
    private IDataInventoryRecordService inventoryRecordService;

    @Autowired
    private ISysUserService userService;

    @Autowired
    private IBaseLimitService limitService;

    /**
     * 查询订单信息列表
     */
    @PreAuthorize("@ss.hasPermi('data:sale:list')")
    @GetMapping("/list")
    public TableDataInfo list(DataSale dataSale) {
        startPage();
        List<DataSale> list = dataSaleService.selectDataSaleList(dataSale);
        return getDataTable(list);
    }

    /**
     * 导出订单信息列表
     */
    @PreAuthorize("@ss.hasPermi('data:sale:export')")
    @Log(title = "订单信息", businessType = BusinessType.EXPORT)
    @PostMapping("/export")
    public void export(HttpServletResponse response, DataSale dataSale) {
        List<DataSale> list = dataSaleService.selectDataSaleList(dataSale);
        ExcelUtil<DataSale> util = new ExcelUtil<DataSale>(DataSale.class);
        util.exportExcel(response, list, "订单信息数据");
    }

    /**
     * 获取订单信息详细信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:query')")
    @GetMapping(value = "/{id}")
    public AjaxResult getInfo(@PathVariable("id") Long id) {
        return AjaxResult.success(dataSaleService.selectDataSaleById(id));
    }

    /**
     * 新增订单信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:add')")
    @Log(title = "订单信息", businessType = BusinessType.INSERT)
    @PostMapping
    public AjaxResult add(@RequestBody DataSale dataSale) {
        BaseLimit limit = limitService.selectBaseLimitUse();
        if (StringUtils.isNull(limit)) {
            return AjaxResult.error("兑换比例未设置");
        }
        dataSale.setGoldScale(Integer.parseInt(limit.getGoldScale()));
        return toAjax(dataSaleService.insertDataSale(dataSale));
    }

    /**
     * 修改订单信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:edit')")
    @Log(title = "订单信息", businessType = BusinessType.UPDATE)
    @PutMapping
    public AjaxResult edit(@RequestBody DataSale dataSale) {
        BaseLimit limit = limitService.selectBaseLimitUse();
        if (StringUtils.isNull(limit)) {
            return AjaxResult.error("兑换比例未设置");
        }
        if (dataSale.getExamStatus().equals("Y")) {
            return AjaxResult.error("订单已审核不可修改");
        }
        dataSale.setGoldScale(Integer.parseInt(limit.getGoldScale()));
        return toAjax(dataSaleService.updateDataSale(dataSale));
    }

    /**
     * 审核订单信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:exam')")
    @Log(title = "订单信息", businessType = BusinessType.UPDATE)
    @PutMapping("/exam")
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult exam(@RequestBody DataSale dataSale) {
        SysUser user = userService.selectUserById(dataSale.getUserId());
        if (StringUtils.isNull(user)) {
            return AjaxResult.error("下单会员不存在");
        }
        SysUser stockUser = userService.selectUserById(dataSale.getStockUserId());
        if (StringUtils.isNull(stockUser)) {
            return AjaxResult.error("报货人不存在");
        }
        if (stockUser.getGoldAvailable() < dataSale.getAllGold()) {
            return AjaxResult.error("报货人金豆不足");
        }
        if (stockUser.getUserAvailable() < dataSale.getAddUser()) {
            return AjaxResult.error("报货人可用名额不足");
        }
        DataInventory inventory;
        //判断库存
        for (DataSaleItem item : dataSale.getDataSaleItemList()) {
            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getStockUserId(), item.getGoodId());
            if (StringUtils.isNull(inventory)) {
                return AjaxResult.error("报货人不存在【" + item.getGoodName() + "】商品");
            } else {
                if (inventory.getAmount() < item.getGoodAmount()) {
                    return AjaxResult.error("报货人可用【" + inventory.getGoodName() + "】库存不足");
                }
            }
        }
        user.setGoldAvailable(user.getGoldAvailable() + dataSale.getAllGold());
        user.setUserAvailable(user.getUserAvailable() + dataSale.getAddUser());
        userService.updateUserProfile(user);

        stockUser.setGoldAvailable(stockUser.getGoldAvailable() - dataSale.getAllGold());
        stockUser.setUserAvailable(stockUser.getUserAvailable() - dataSale.getAddUser());
        userService.updateUserProfile(stockUser);

        LoginUser loginUser = getLoginUser();
        dataSale.setExamStatus("Y");
        dataSale.setExamBy(loginUser.getUserId());
        dataSale.setExamName(loginUser.getUser().getNickName());
        dataSale.setExamTime(DateUtils.getNowDate());
        dataSaleService.updateDataSaleExam(dataSale);

        DataInventoryRecord inventoryRecord;
        for (DataSaleItem item : dataSale.getDataSaleItemList()) {
            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getStockUserId(), item.getGoodId());
            inventory.setAmount(inventory.getAmount() - item.getGoodAmount());
            inventoryService.updateDataInventory(inventory);
            //添加报货人减少库存记录
            inventoryRecord = new DataInventoryRecord();
            inventoryRecord.setDeptId(stockUser.getDeptId());
            inventoryRecord.setUserId(stockUser.getUserId());
            inventoryRecord.setNickName(stockUser.getNickName());
            inventoryRecord.setBillNumber(dataSale.getBillNumber());
            inventoryRecord.setGoodId(item.getGoodId());
            inventoryRecord.setGoodCode(item.getGoodCode());
            inventoryRecord.setGoodName(item.getGoodName());
            inventoryRecord.setAmount(0 - item.getGoodAmount());
            inventoryRecord.setInAmount(0);
            inventoryRecord.setOutAmount(item.getGoldAmount());
            inventoryRecord.setStockType(SystemType.OUT.getCode());
            inventoryRecord.setStockDesc("订单审核减少：" + item.getGoldAmount() + "金豆。单号:" + dataSale.getBillNumber() +
                    "---审核人：【" + dataSale.getExamName() + "】" +
                    "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
            inventoryRecordService.insertDataInventoryRecord(inventoryRecord);

            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getUserId(), item.getGoodId());
            if (StringUtils.isNull(inventory)) {
                inventory = new DataInventory();
                inventory.setDeptId(dataSale.getDeptId());
                inventory.setUserId(dataSale.getUserId());
                inventory.setNickName(dataSale.getNickName());
                inventory.setGoodId(item.getGoodId());
                inventory.setGoodCode(item.getGoodCode());
                inventory.setGoodName(item.getGoodName());
                inventory.setAmount(item.getGoodAmount());
                inventoryService.insertDataInventory(inventory);
            } else {
                inventory.setAmount(inventory.getAmount() + item.getGoodAmount());
                inventoryService.updateDataInventory(inventory);
            }
            //添加提报人增加库存记录
            inventoryRecord = new DataInventoryRecord();
            inventoryRecord.setDeptId(dataSale.getDeptId());
            inventoryRecord.setUserId(dataSale.getUserId());
            inventoryRecord.setNickName(dataSale.getNickName());
            inventoryRecord.setBillNumber(dataSale.getBillNumber());
            inventoryRecord.setGoodId(item.getGoodId());
            inventoryRecord.setGoodCode(item.getGoodCode());
            inventoryRecord.setGoodName(item.getGoodName());
            inventoryRecord.setAmount(item.getGoodAmount());
            inventoryRecord.setInAmount(item.getGoldAmount());
            inventoryRecord.setOutAmount(0);
            inventoryRecord.setStockType(SystemType.IN.getCode());
            inventoryRecord.setStockDesc("订单审核增加：" + item.getGoldAmount() + "金豆。单号:" + dataSale.getBillNumber() +
                    "---审核人：【" + dataSale.getExamName() + "】" +
                    "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
            inventoryRecordService.insertDataInventoryRecord(inventoryRecord);
        }

        //添加金豆记录
        DataGold gold = new DataGold();
        gold.setDeptId(dataSale.getDeptId());
        gold.setUserId(dataSale.getUserId());
        gold.setNickName(dataSale.getNickName());
        gold.setGold(dataSale.getAllGold());
        gold.setGoldCurrent(user.getGoldAvailable());
        gold.setGoldType(SystemType.IN.getCode());
        gold.setGoldDesc("订单审核增加：" + gold.getGold() + "金豆。单号:" + dataSale.getBillNumber() +
                "---审核人：【" + dataSale.getExamName() + "】" +
                "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
        goldService.insertDataGold(gold);

        //减少金豆记录
        DataGold stockGold = new DataGold();
        stockGold.setDeptId(stockUser.getDeptId());
        stockGold.setUserId(stockUser.getUserId());
        stockGold.setNickName(stockUser.getNickName());
        stockGold.setGold(dataSale.getAllGold());
        stockGold.setGoldCurrent(stockUser.getGoldAvailable());
        stockGold.setGoldType(SystemType.OUT.getCode());
        stockGold.setGoldDesc("订单审核减少：" + stockGold.getGold() + "金豆。单号:" + dataSale.getBillNumber() +
                "---审核人：【" + dataSale.getExamName() + "】" +
                "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
        goldService.insertDataGold(stockGold);

        return AjaxResult.success();
    }

    /**
     * 撤销订单信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:cancel')")
    @Log(title = "订单信息", businessType = BusinessType.UPDATE)
    @PutMapping("/cancel")
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult cancel(@RequestBody DataSale dataSale) {
        SysUser user = userService.selectUserById(dataSale.getUserId());
        if (StringUtils.isNull(user)) {
            return AjaxResult.error("下单会员不存在");
        }
        SysUser stockUser = userService.selectUserById(dataSale.getStockUserId());
        if (StringUtils.isNull(stockUser)) {
            return AjaxResult.error("报货人不存在");
        }
        if (user.getGoldAvailable() < dataSale.getAllGold()) {
            return AjaxResult.error("可用金豆不足，不可撤销");
        }
        if (user.getUserAvailable() < dataSale.getAddUser()) {
            return AjaxResult.error("可用名额不足，不可撤销");
        }
        DataInventory inventory;
        //判断库存
        for (DataSaleItem item : dataSale.getDataSaleItemList()) {
            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getUserId(), item.getGoodId());
            if (StringUtils.isNull(inventory)) {
                return AjaxResult.error("提交人不存在【" + item.getGoodName() + "】商品");
            } else {
                if (inventory.getAmount() < item.getGoodAmount()) {
                    return AjaxResult.error("提交人可用【" + inventory.getGoodName() + "】库存不足");
                }
            }
        }
        user.setGoldAvailable(user.getGoldAvailable() - dataSale.getAllGold());
        user.setUserAvailable(user.getUserAvailable() - dataSale.getAddUser());
        userService.updateUserProfile(user);

        stockUser.setGoldAvailable(stockUser.getGoldAvailable() + dataSale.getAllGold());
        stockUser.setUserAvailable(stockUser.getUserAvailable() + dataSale.getAddUser());
        userService.updateUserProfile(stockUser);

        dataSaleService.updateDataSaleCancel(dataSale);

        DataInventoryRecord inventoryRecord;
        for (DataSaleItem item : dataSale.getDataSaleItemList()) {
            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getStockUserId(), item.getGoodId());
            inventory.setAmount(inventory.getAmount() + item.getGoodAmount());
            inventoryService.updateDataInventory(inventory);
            //添加报货人增加库存记录
            inventoryRecord = new DataInventoryRecord();
            inventoryRecord.setDeptId(stockUser.getDeptId());
            inventoryRecord.setUserId(stockUser.getUserId());
            inventoryRecord.setNickName(stockUser.getNickName());
            inventoryRecord.setBillNumber(dataSale.getBillNumber());
            inventoryRecord.setGoodId(item.getGoodId());
            inventoryRecord.setGoodCode(item.getGoodCode());
            inventoryRecord.setGoodName(item.getGoodName());
            inventoryRecord.setAmount(item.getGoodAmount());
            inventoryRecord.setInAmount(item.getGoodAmount());
            inventoryRecord.setOutAmount(0);
            inventoryRecord.setStockType(SystemType.IN.getCode());
            inventoryRecord.setStockDesc("订单撤销增加：" + item.getGoldAmount() + "金豆。单号:" + dataSale.getBillNumber() +
                    "---审核人：【" + dataSale.getExamName() + "】" +
                    "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
            inventoryRecordService.insertDataInventoryRecord(inventoryRecord);

            inventory = inventoryService.selectDataInventoryByUserIdAndGoodId(dataSale.getUserId(), item.getGoodId());
            inventory.setAmount(inventory.getAmount() - item.getGoodAmount());
            inventoryService.updateDataInventory(inventory);
            //添加提报人减少库存记录
            inventoryRecord = new DataInventoryRecord();
            inventoryRecord.setDeptId(dataSale.getDeptId());
            inventoryRecord.setUserId(dataSale.getUserId());
            inventoryRecord.setNickName(dataSale.getNickName());
            inventoryRecord.setBillNumber(dataSale.getBillNumber());
            inventoryRecord.setGoodId(item.getGoodId());
            inventoryRecord.setGoodCode(item.getGoodCode());
            inventoryRecord.setGoodName(item.getGoodName());
            inventoryRecord.setAmount(0 - item.getGoldAmount());
            inventoryRecord.setInAmount(0);
            inventoryRecord.setOutAmount(item.getGoldAmount());
            inventoryRecord.setStockType(SystemType.OUT.getCode());
            inventoryRecord.setStockDesc("订单撤销减少：" + item.getGoldAmount() + "金豆。单号:" + dataSale.getBillNumber() +
                    "---审核人：【" + dataSale.getExamName() + "】" +
                    "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
            inventoryRecordService.insertDataInventoryRecord(inventoryRecord);
        }

        //减少金豆记录
        DataGold gold = new DataGold();
        gold.setDeptId(dataSale.getDeptId());
        gold.setUserId(dataSale.getUserId());
        gold.setNickName(dataSale.getNickName());
        gold.setGold(dataSale.getAllGold());
        gold.setGoldCurrent(user.getGoldAvailable());
        gold.setGoldType(SystemType.OUT.getCode());
        gold.setGoldDesc("订单撤销减少：" + gold.getGold() + "金豆。单号:" + dataSale.getBillNumber() +
                "---审核人：【" + dataSale.getExamName() + "】" +
                "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
        goldService.insertDataGold(gold);

        //增加金豆记录
        DataGold stockGold = new DataGold();
        stockGold.setDeptId(stockUser.getDeptId());
        stockGold.setUserId(stockUser.getUserId());
        stockGold.setNickName(stockUser.getNickName());
        stockGold.setGold(dataSale.getAllGold());
        stockGold.setGoldCurrent(stockUser.getGoldAvailable());
        stockGold.setGoldType(SystemType.IN.getCode());
        stockGold.setGoldDesc("订单撤销增加：" + stockGold.getGold() + "金豆。单号:" + dataSale.getBillNumber() +
                "---审核人：【" + dataSale.getExamName() + "】" +
                "---审核时间：【" + DateUtils.parseDateToStr("yyyy-MM-dd HH:mm:ss", dataSale.getExamTime()) + "】");
        goldService.insertDataGold(stockGold);

        return toAjax(dataSaleService.updateDataSaleCancel(dataSale));
    }

    /**
     * 删除订单信息
     */
    @PreAuthorize("@ss.hasPermi('data:sale:remove')")
    @Log(title = "订单信息", businessType = BusinessType.DELETE)
    @DeleteMapping("/{ids}")
    public AjaxResult remove(@PathVariable Long[] ids) {
        return toAjax(dataSaleService.deleteDataSaleByIds(ids));
    }
}
